using System;
using System.Collections.Generic;
using System.Text;
using DBConnectionLib;
using System.Collections.Specialized;
using System.Linq;

namespace DBSourceToolsLib
{
    public class DatabaseEx : Database
    {
//        protected SysObjects.SysObjects m_SysObjects;
        private DatabaseCreateScript m_CreateScript;
        private DatabaseDropScript m_DropScript;

        #region getters and setters
        public DatabaseCreateScript CreateScript
        {
            get { return m_CreateScript; }
            set { m_CreateScript = value; }
        }

        public DatabaseDropScript DropScript
        {
            get { return m_DropScript; }
            set { m_DropScript = value; }
        }

//        public SysObjects.SysObjects SysObjects
//        {
//            get { return m_SysObjects; }
////            set { m_SysObjects = value; }
//        }
        #endregion
        public DatabaseEx(DBConnectionLib.Database oBaseDB, bool isDeploymentTarget)
            //: base(oBaseDB.Name,
            //oBaseDB.DataSourceName, oBaseDB.DatabaseName, oBaseDB.BaseDirectory)
        {
            this.m_Name = oBaseDB.NickName;
            this.m_DataSourceName = oBaseDB.DataSourceName;
            this.m_DatabaseName = oBaseDB.DatabaseName;
            this.m_ConnectionString = oBaseDB.ConnectionString;
            this.m_BaseDirectory = oBaseDB.BaseDirectory;
            this.m_UserName = oBaseDB.UserName;
            this.Password = oBaseDB.Password;
            
            this.IsDeploymentTarget = isDeploymentTarget;
//            this.SysObjects.ScriptOptions. = this.m_BaseDirectory + "\\ScriptOptions

            if (isDeploymentTarget)
            {
                this.m_DropScript = new DatabaseDropScript(this, null);
                this.m_CreateScript = new DatabaseCreateScript(this, null);
            }
        }

        public DatabaseEx(DBConnectionLib.Database oBaseDB, bool isDeploymentTarget, DatabaseEx oParentDatabase)
        {
            this.m_Name = oBaseDB.NickName;
            this.m_DataSourceName = oBaseDB.DataSourceName;
            this.m_DatabaseName = oBaseDB.DatabaseName;
            this.m_ConnectionString = oBaseDB.ConnectionString;
            this.m_BaseDirectory = oBaseDB.BaseDirectory;
            this.m_UserName = oBaseDB.UserName;
            this.Password = oBaseDB.Password;
            //this.m_SysObjects = new DBSourceToolsLib.SysObjects.SysObjects(this, this.m_BaseDirectory);
            this.IsDeploymentTarget = isDeploymentTarget;

            if (isDeploymentTarget)
            {
                this.m_DropScript = new DatabaseDropScript(this, null);
                this.m_CreateScript = new DatabaseCreateScript(this, null);
//                this.SysObjects.ScriptOptions = new DatabaseScriptOptions(oParentDatabase);

            }
        }


        public void AddDropAndCreateScript(DatabaseEx sourceDatabase)
        {
            this.m_DropScript = new DatabaseDropScript(this, sourceDatabase);
            this.m_DropScript.LoadScriptFromDatabase();
            this.m_CreateScript = new DatabaseCreateScript(this, sourceDatabase);
            this.m_CreateScript.LoadScriptFromDatabase();
        }

        public void CreateMyDirectory()
        {
            if (!System.IO.Directory.Exists(this.BaseDirectory))
                System.IO.Directory.CreateDirectory(this.BaseDirectory);

        }

        public void ForceDrop()
        {
            Microsoft.SqlServer.Management.Smo.Server oServer = this.GetSmoServer();
            oServer.KillDatabase(this.DatabaseName);
            //Microsoft.SqlServer.Management.Smo.Database oMDatabase = this.GetSmoDatabase(oServer);
            //int iConnCount = oMDatabase.ActiveConnections;
            //oMDatabase.SetOffline();
            //oMDatabase.Drop();

        }

        public bool VerifyCreateScript(string strCreateScriptControl)
        {
            if (!System.IO.File.Exists(strCreateScriptControl))
                throw new Exception("Cannot find " + strCreateScriptControl);

            bool bAllFound = true;
            using (System.IO.StreamReader oReader = new System.IO.StreamReader(strCreateScriptControl))
            {
                string strLine;
                List<string> oFileLines = new List<string>();
                while ((strLine = oReader.ReadLine()) != null)
                    oFileLines.Add(strLine);

                List<string> oPaths = oFileLines.Where(line => line.Contains("FILENAME")).ToList();
                foreach (string strPathLine in oPaths)
                {
                    string[] arrValues = strPathLine.Split('\'');
                    foreach (string strValue in arrValues)
                    {
                        if (strValue.Contains('\\'))
                            bAllFound = bAllFound && ValidatePath(strValue);
                    }
                }
            }
            return bAllFound;
        }

        private bool ValidatePath(string strValueString)
        {
            string [] strArr = strValueString.Split('\'');
            foreach (string strValue in strArr)
            {
                if (strValue.Contains('\\'))
                {
                    string strDir = strValue.Substring(0, strValue.LastIndexOf('\\'));
                    if (!System.IO.Directory.Exists(strDir))
                        return false;
                }

            }
            return true;
        }

        public bool CanCompare()
        {
            return (GetSmoServer().VersionMajor > 8);
        }
    }
}
